package name.fowler.refactoring.simplestore;

import java.util.ArrayList;
import java.util.List;

public class Customer {
	private static final int AMOUNT_MULTYPLAY_NEWRELEASE_FILM = 3;
	private static final double AMOUNT_INCREMENT_CHILDRENS_FILM = 1.5;
	private static final int AMOUNT_INCREMET_REGULAR_FILM = 2;
	private static final double PAYMENT_PERCENT = 1.5;
	private static final int THREE_DAY_DAYS_RENTED = 3;
	private static final int TWO_DAY_DAYS_RENTED = 2;
	private static final int ONE_DAY_DAYS_RENTED = 1;
	private String customerName;
	private List<Rental> movieRentals = new ArrayList<Rental>();

	public Customer(String name) {
		this.customerName = name;
	}

	public String getName() {
		return customerName;
	}


	public void addRental(Rental arg){
		movieRentals.add(arg);
	}

	public String Statement()
	{
		double totalAmount = 0;
		int frequentRenterPoints = 0;
				
		String result = "Rental record for " + customerName + "\n";
		
		for(Rental each: movieRentals) {
			double thisAmount = 0;
			
			// Determine amounts for each line
			switch(each.getMovie().getPriceCode()) {
				case Regular:
				thisAmount = calculateAmountForRegular(each, thisAmount);
					break;
	
				case NewRelease:
				thisAmount = calculateAmountForNewRelease(each, thisAmount);
					break;
	
				case Childrens:
				thisAmount = calculateAmountForChildrens(each, thisAmount);
					break;
			}

			frequentRenterPoints++;

			if (checkBonus(each))
			{
				frequentRenterPoints ++;
			}

			result += "\t" + each.getMovie().getTitle() + "\t" + thisAmount + "\n";
			totalAmount += thisAmount;
		}

		result += "Amount owed is " + totalAmount + "\n";
		result += "You earned " + frequentRenterPoints + " frequent renter points.";
		return result;
	}

	private double calculateAmountForChildrens(Rental each, double thisAmount) {
		thisAmount += AMOUNT_INCREMENT_CHILDRENS_FILM;
		if (each.getDaysRented() > THREE_DAY_DAYS_RENTED)
		{
			thisAmount = (each.getDaysRented() - THREE_DAY_DAYS_RENTED) * PAYMENT_PERCENT;
		}
		return thisAmount;
	}

	private double calculateAmountForNewRelease(Rental each, double thisAmount) {
		thisAmount += each.getDaysRented() * AMOUNT_MULTYPLAY_NEWRELEASE_FILM;
		return thisAmount;
	}

	private double calculateAmountForRegular(Rental each, double thisAmount) {
		thisAmount += AMOUNT_INCREMET_REGULAR_FILM;
		if (each.getDaysRented() > TWO_DAY_DAYS_RENTED)
		{
			thisAmount += (each.getDaysRented() - TWO_DAY_DAYS_RENTED) * PAYMENT_PERCENT;
		}
		return thisAmount;
	}

	private boolean checkBonus(Rental each) {
		return (each.getMovie().getPriceCode() == PriceCodes.NewRelease) && (each.getDaysRented() > ONE_DAY_DAYS_RENTED);
	}
}

